﻿using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Aribaccio.Core
{
    /// <summary>
    /// 内置IOC容器管理
    /// </summary>
    public class ContainerManager : Singleton<ContainerManager>, IContainerManager
    {
        /// <summary>
        /// 基础路径
        /// </summary>
        public string BasePath { get; set; }
        /// <summary>
        /// 基础路径下配置文件
        /// </summary>
        public string ConfigFileJson { get; set; }
        /// <summary>
        /// 容器服务配置对象
        /// </summary>
        public IConfiguration Configuration { get; set; }
        /// <summary>
        /// 容器服务配置构造对象
        /// </summary>
        public IConfigurationBuilder ConfigurationBuilder { get; set; }
        /// <summary>
        /// 容器服务注册对象
        /// </summary>
        public IServiceCollection ServiceCollection { get; set; }
        /// <summary>
        /// 容器服务构造对象
        /// </summary>
        public IServiceProvider ServiceProvider { get; set; }

        /// <summary>
        /// 默认构造函数[私有单例]
        /// </summary>
        public ContainerManager()
        {
            this.BasePath = Directory.GetCurrentDirectory();
            this.ConfigFileJson = string.Empty;
            // ConfigurationBuilder 引用 Microsoft.Extensions.Configuration
            //初始化构建容器服务配置构造对象
            this.ConfigurationBuilder = new ConfigurationBuilder();
            //初始化构建容器服务配置对象
            this.Configuration = this.ConfigurationBuilder.Build();

            // ServiceCollection 引用 Microsoft.Extensions.DependencyInjection;
            //初始化构建容器服务注册对象
            this.ServiceCollection = new ServiceCollection();
            //初始化构建容器服务构造对象
            this.ServiceProvider = this.ServiceCollection.BuildServiceProvider();
        }
        /// <summary>
        /// 构建容器配置
        /// </summary>
        public void BuildConfig(string argConfigFileJson)
        {
            this.ConfigFileJson = argConfigFileJson;
            //判断检查
            if (this.ConfigurationBuilder == null) this.ConfigurationBuilder = new ConfigurationBuilder();
            //重新构建配置路径，文件
            this.ConfigurationBuilder
                .SetBasePath(this.BasePath)
                .AddJsonFile(this.ConfigFileJson, optional: false, reloadOnChange: true);
            //重新构建容器服务配置对象
            this.Configuration = this.ConfigurationBuilder.Build();
        }
        /// <summary>
        /// 构建容器服务
        /// </summary>
        /// <param name="argBasePath">基础路径</param>
        /// <param name="argJsonConfigFile">基础路径下配置文件</param>
        public void BuildService()
        {
            //判断检查
            if (this.ServiceCollection == null) this.ServiceCollection = new ServiceCollection();
            //重新构建容器服务构造对象
            this.ServiceProvider = this.ServiceCollection.BuildServiceProvider();
        }
        /// <summary>
        /// 获取构建的服务对象
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <returns></returns>
        public T? GetContainerService<T>() where T : class
        {
            return this.ServiceProvider != null ? this.ServiceProvider.GetService<T>() : null;
        }
        /// <summary>
        /// 获取构建的请求服务对象
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <returns></returns>
        public T? GetContainerServiceRequired<T>() where T : class
        {
            return this.ServiceProvider != null ? this.ServiceProvider.GetRequiredService<T>() : null;
        }
    }
}
